using FibMatrix.Task;
using UnityEngine;
using UnityEngine.Profiling;

namespace FibMatrix
{
	[FM_Mono.IgnoreGen]
	public class AsyncLoadAssetFromBundlePipe : IResourceLoadPipe
	{
		public FMTask Handle(IResourcePipelineContext rawContext, out ResourceError error)
		{
			Profiler.BeginSample("AsyncLoadAssetFromBundlePipe.Handle");
			error = ResourceError.None;
			ResourcePipelineContext context = rawContext as ResourcePipelineContext;
			AssetBundleLoadItem mainHint = context.item as AssetBundleLoadItem;
			if (mainHint.bundleInfo.node.isAssetBundleFile == false)
				return null;

			FMTask task = null;
			if (mainHint.assetHandle == null)
			{
				if (mainHint.bundleHandle != null)
				{
					if (!mainHint.bundleHandle.isCompleted)
					{
						error = ResourceError.BundleRequestNotComplete;
						Profiler.EndSample();
						return null;
					}
					// todo, 移动到task里
					mainHint.assetHandle = mainHint.bundleHandle.LoadAssetAsync(mainHint.itemID, context.type);
					if (mainHint.assetHandle != null)
					{
						++mainHint.objRefCount;
						if (!mainHint.assetHandle.isCompleted)
						{
							task = PooledAsyncFMTask.Allocate(mainHint, null, GenerateAssetAsyncWork, GetAsyncAssetWorkError, null);
							task.Begin();
						}
					}
				}
			}
			else if (!mainHint.assetHandle.isCompleted)
			{
				task = PooledAsyncFMTask.Allocate(context, null, GenerateAssetAsyncWork, GetAsyncAssetWorkError, null);
				task.Begin();
			}
			else
			{
				task = PooledCallLaterFMTask.Allocate(1);
				task.Begin();
			}


			if (mainHint.assetHandle == null)
			{
				error = ResourceError.AssetLoadError;
				Debug.LogError($"LoadAssetAsyncInBundle failed:{mainHint.itemID}, error:{error}");
			}

			Profiler.EndSample();
			return task;
		}

		private static IAsyncBase GenerateAssetAsyncWork(PooledAsyncFMTask task)
		{
			AssetBundleLoadItem item = (task.context as AssetBundleLoadItem);
			return item.assetHandle;
		}

		private static ResourceError GetAsyncAssetWorkError(PooledAsyncFMTask task, IAsyncBase asyncWork)
		{
			var loadHandle = (asyncWork as BundleLoadAssetHandle);
			if (loadHandle == null || loadHandle.asset == null)
			{
				Debug.LogError($"LoadAssetAsyncInBundle failed:{ResourceError.AssetLoadError}");
				return ResourceError.AssetLoadError;
			}

			return ResourceError.None;
		}
		
		//private static void ProcessAssetAsyncWorkResult(PooledAsyncRETask task, IAsyncBase asyncWork)
		//   {
		//	var context = (task.context as IResourcePipelineContext);
		//	var mainHint = context.item as AssetBundleLoadItem;
		//	if (mainHint.original == null)
		//	{
		//		SetBundleHintObjectInfo(mainHint, context);
		//	}
		//	else
		//       {
		//		--mainHint.objRefCount;
		//       }
		//}
	}
}
